package com.anxin.act.process.web;

import com.anxin.act.busFlow.entity.WfBusNode;
import com.anxin.act.busFlow.service.WfBusNodeService;
import com.anxin.act.process.dao.ActProcessDao;
import com.anxin.act.process.dto.CcProcessDTO;
import com.anxin.act.process.service.ActProcessService;
import com.anxin.act.process.service.ProcessEndService;
import com.anxin.act.process.service.ProcessStartService;
import com.anxin.act.process.vo.ProcessVo;
import com.anxin.act.process.vo.RuProcessVo;
import com.anxin.act.task.service.ActSendTaskService;
import com.anxin.act.task.service.ActSpecialTaskService;
import com.anxin.act.task.service.WfCcRecordService;
import com.anxin.act.task.vo.HiTaskVo;
import com.anxin.act.utils.ActProcessUtils;
import com.anxin.common.utils.LogUtils;
import com.anxin.common.utils.StringUtils;
import com.anxin.common.utils.sys.UserUtils;
import com.anxin.framework.aspectj.lang.annotation.Log;
import com.anxin.framework.aspectj.lang.enums.BusinessType;
import com.anxin.framework.web.controller.BaseController;
import com.anxin.framework.web.entity.AjaxResult;
import com.anxin.framework.web.page.TableDataInfo;
//import io.swagger.annotations.Api;
//import io.swagger.annotations.ApiOperation;
import org.activiti.engine.HistoryService;
import org.activiti.engine.TaskService;
import org.activiti.engine.history.HistoricActivityInstance;
import org.activiti.engine.history.HistoricProcessInstance;
import org.activiti.engine.history.HistoricTaskInstance;
import org.activiti.engine.runtime.ProcessInstance;
import org.activiti.engine.task.Comment;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletResponse;
import javax.xml.stream.XMLStreamException;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

/**
 * 流程管理
 * @author: liuxiangyu
 * @date: 2020/3/9 15:19
 */
//@Api(tags = "流程管理")
@RestController
@RequestMapping("/act/process")
public class ActProcessController extends BaseController {
    private static Logger logger = LoggerFactory.getLogger("sys-error");

    @Autowired
    private ActProcessService actProcessService;

    @Autowired
    private ProcessStartService processStartService;

    @Autowired
    private ProcessEndService processEndService;

    @Autowired
    private ActSendTaskService actSendTaskService;

    @Autowired
    private ActSpecialTaskService actSpecialTaskService;


    /**
     * 启动流程
     * @returnssss
     */
    //@ApiOperation(value="启动流程",notes="作者:刘翔宇",position = 1)
    @PostMapping("/startProcess")
    @Log(title = "启动流程", businessType = BusinessType.INSERT)
    public AjaxResult startProcess(@RequestBody RuProcessVo ruProcessVo) {
        //流程启动前的校验
        AjaxResult ajaxResult = processStartService.startCheck(ruProcessVo.getDataTable(), ruProcessVo.getDataId());
        if (200 != ajaxResult.getCode()) {
            return ajaxResult;
        }
        //启动流程
        ProcessInstance processInstance = actProcessService.startProcess(ruProcessVo);

        // 校验流程是否到了某个特殊节点
        actSpecialTaskService.checkSpecialNode(processInstance.getProcessInstanceId());

        //判断流程是否结束,如果结束了则执行结束后需调用的方法
        processEndService.whetherToEnd(processInstance.getId());
        return AjaxResult.success();
    }

    /**
     * 查询我的申请
     * @return
     */
    //@ApiOperation(value="查询我的申请",notes="作者:刘翔宇",position = 2)
    @GetMapping("/applyList")
    @Log(title = "查询我的申请", businessType = BusinessType.LIST, importentName = "title")
    public TableDataInfo<ProcessVo> applyList(ProcessVo processVo){
        processVo.setApplyUserName(UserUtils.getUserName());
        return actProcessService.processList(processVo);
    }


    /**
     * 查询全部流程
     * @return
     */
    //@ApiOperation(value="查询全部流程",notes="作者:刘翔宇",position = 2)
    @GetMapping("/allList")
    @Log(title = "查询全部流程", businessType = BusinessType.LIST)
    public TableDataInfo<ProcessVo> allList(ProcessVo processVo){
        return actProcessService.processList(processVo);
    }



    /**
     * 终止流程
     * @return
     */
    //@ApiOperation(value="终止流程",notes="作者:刘翔宇",position = 3)
    @PostMapping("/stopProcess")
    @Log(title = "终止流程", businessType = BusinessType.UPDATE)
    public AjaxResult stopProcess(@RequestParam(value="actId",required = true) String actId,@RequestParam(value="reason",required = true) String reason){
        return actProcessService.stopProcess(actId,reason);
    }


    /**
     * 查询流程审批记录
     * @param actId
     * @return
     */
    //@ApiOperation(value="查询流程审批记录",notes="作者:刘翔宇",position = 4)
    @GetMapping("/approvalRecord")
    @Log(title = "查询流程审批记录", businessType = BusinessType.LIST)
    public AjaxResult<List<HiTaskVo>> approvalRecord(String actId, String sid){
        return actProcessService.approvalRecord(actId, sid);
    }


    /**
     * 删除可用流程
     * @param deploymentId
     * @return
     */
    //@ApiOperation(value="删除可用流程",notes="作者:刘翔宇",position = 4)
    @GetMapping("/delProcess/{deploymentId}")
    @Log(title = "删除可用流程", businessType = BusinessType.DELETE)
    public AjaxResult delProcess(@PathVariable("deploymentId")String deploymentId){

        return actProcessService.delProcess(deploymentId);
    }


    /**
     * 查询流程列表
     * @param processVo
     * @return
     */
    //@ApiOperation(value="查询流程列表(分页)",notes="作者:刘翔宇",position = 5 )
    @PreAuthorize("@ss.hasPermi('act:process:view')")
    @GetMapping("/list")
    @Log(title = "查询流程XML", businessType = BusinessType.LIST)
    public TableDataInfo list(ProcessVo processVo){
        return actProcessService.findList(processVo);
    }

    /**
     * 查询流程列表，不带分页，用户选择流程的下拉框
     * @return
     */
    //@ApiOperation(value="查询流程列表(不分页)",notes="作者:刘翔宇",position = 4 )
    @GetMapping("/listData")
    @Log(title = "查询流程列表(不分页)", businessType = BusinessType.LIST)
    public AjaxResult listData(){
        return AjaxResult.success(actProcessService.listData());
    }

    /**
     * 获取流程XML
     * @param procDefId
     * @return
     */
    //@ApiOperation(value="查询流程XML",notes="作者:刘翔宇",position = 5 )
    @GetMapping("/getXml/{procDefId}")
    @Log(title = "查询流程XML", businessType = BusinessType.LIST)
    public AjaxResult getXml(@PathVariable("procDefId")String procDefId){
        return actProcessService.getXml(procDefId);
    }


    /**
     * 获取流程图XML
     * @param actId
     * @return
     */
    //@ApiOperation(value="查询流程XML",notes="作者:杨浩")
    @GetMapping("/genProcessDiagram/{actId}")
    @Log(title = "查询流程XML", businessType = BusinessType.LIST)
    public AjaxResult genProcessDiagram(@PathVariable("actId")String actId){
        return AjaxResult.success(actProcessService.genProcessDiagram(actId));
    }

    /**
     * 根据流程定义ID获取流程图XML
     * @param processDefinitionKey 流程实例ID
     *
     * @return
     */
    //@ApiOperation(value="根据流程定义ID获取流程图",notes="作者:刘翔宇",position = 6 )
    @GetMapping("/genProcessFormDiagram/{processDefinitionKey}")
    @Log(title = "查询流程图片", businessType = BusinessType.LIST)
    public AjaxResult genProcessFormDiagram(@PathVariable("processDefinitionKey") String processDefinitionKey) {
        return AjaxResult.success(actProcessService.genProcessFormDiagram(processDefinitionKey));
    }
    /**
     * 获取流程图
     * @param actId 流程实例ID
     * @return
     */
    //@ApiOperation(value="查询流程图片",notes="作者:刘翔宇",position = 6 )
    @GetMapping("/getPhoto/{actId}")
    @Log(title = "查询流程图片", businessType = BusinessType.LIST)
    public AjaxResult getPhoto(@PathVariable("actId")String actId) throws IOException {
        return actProcessService.getProcessPhoto(actId);
    }

    /**
     * 根据流程定义ID获取流程图
     * @param processDefinitionKey 流程实例ID
     * @return
     */
    //@ApiOperation(value="根据流程定义ID获取流程图",notes="作者:刘翔宇",position = 6 )
    @GetMapping("/showFlowChart/{processDefinitionKey}")
    @Log(title = "查询流程图片", businessType = BusinessType.LIST)
    public AjaxResult showFlowChart(@PathVariable("processDefinitionKey") String processDefinitionKey) {
        return actProcessService.showFlowChart(processDefinitionKey);
    }

    /**
     * 根据流程定义ID查询流程审批人
     * @param processDefinitionKey 流程实例ID
     * @return
     */
    //@ApiOperation(value="根据流程定义ID查询流程审批人",notes="作者:刘翔宇",position = 6 )
    @GetMapping("/showFlowAssignees/{processDefinitionKey}")
    @Log(title = "查询流程图片", businessType = BusinessType.LIST)
    public AjaxResult showFlowAssignees(@PathVariable("processDefinitionKey") String processDefinitionKey){
        try {
            return actProcessService.showFlowAssignees(processDefinitionKey);
        } catch (Exception e) {
            LogUtils.error(e.getMessage(),e);
        }
        return null;
    }

    /**
     * 根据流程实例ID和节点aid获取没有审批过的节点数据
     * @param actId
     * @return
     */
    //@ApiOperation(value="根据流程实例ID和节点aid获取没有审批过的节点数据",notes="作者:杨浩",position = 4)
    @GetMapping("/showNodeAssignees/{actId}/{sid}")
    @Log(title = "根据流程实例ID和节点aid获取没有审批过的节点数据", businessType = BusinessType.LIST)
    public AjaxResult<List<HiTaskVo>> showNodeAssignees(@PathVariable("actId") String actId,@PathVariable("sid") String sid){
        try {
            return actProcessService.showNodeAssignees(actId, sid);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }
    /**
     * 根据流程实例Key和节点aid获取没有审批过的节点数据
     * @param processKey
     * @return
     */
    //@ApiOperation(value="根据流程实例Key和节点aid获取没有审批过的节点数据",notes="作者:杨浩",position = 4)
    @GetMapping("/showNodeFormAssignees/{processKey}/{sid}")
    @Log(title = "根据流程实例ID和节点aid获取没有审批过的节点数据", businessType = BusinessType.LIST)
    public AjaxResult<List<HiTaskVo>> showNodeFormAssignees(@PathVariable("processKey") String processKey,@PathVariable("sid") String sid){
        try {
            return actProcessService.showNodeFormAssignees(processKey, sid);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }
    /**
     * 查询流程详情
     * @param actId
     * @return
     */
    @GetMapping("/getProcessInfo/{actId}")
    @Log(title = "查询流程详情", businessType = BusinessType.LIST)
    public AjaxResult<RuProcessVo> getProcessInfo(@PathVariable("actId")String actId){
        return actProcessService.getProcessInfo(actId);
    }

    /**
     * 根据processKey 获取那些节点需要选择审批人
     * @param processKey 流程定义的Key
     * @return
     */
    //@ApiOperation(value="根据processKey 获取那些节点需要选择审批人",notes="作者:刘翔宇",position = 3)
    @GetMapping("/getApplyChoiceByKey/{processKey}")
    @Log(title = "根据processKey 获取那些节点需要选择审批人", businessType = BusinessType.LIST)
    public AjaxResult<String> getApplyChoiceByKey(@PathVariable("processKey")String processKey){
        return actProcessService.getApplyChoiceByKey(processKey);
    }

    /**
     * 我的申请催办功能
     */
    //@ApiOperation(value="我的申请催办功能")
    @GetMapping("/hastenWork/{actId}")
    public AjaxResult hastenWork(@PathVariable("actId")String actId){
        // 发送待办提醒
        actSendTaskService.sendTask(actId,"hastenWork");
        return AjaxResult.success();
    }

    /**
     * 流程传阅
     */
    //@ApiOperation(value="流程抄送")
    @PostMapping("/ccProcess")
    @Log(title = "流程抄送", businessType = BusinessType.SAVE)
    public AjaxResult ccProcess(@RequestBody CcProcessDTO ccProcessDTO){
        actProcessService.ccProcess(ccProcessDTO);

        return AjaxResult.success();
    }

    //@ApiOperation(value="恢复流程")
    @GetMapping("/restore/{actId}")
    public AjaxResult restore(@PathVariable("actId")String actId){
        return actProcessService.restore(actId);
    }
}
